package com.xiaobai.service.achievement.v2;

import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.xiaobai.dao.AchievementDao;
import com.xiaobai.mybatis_plus.entity.Achievement;
import com.xiaobai.mybatis_plus.service.IIAchievementService;
import com.xiaobai.vo.AchievementItem;
import lombok.Data;
import lombok.extern.slf4j.Slf4j;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.io.UnsupportedEncodingException;
import java.util.*;

@Slf4j
@Service
public class AchievementServiceV2 implements IAchievementServiceV2 {

    private static final String URL = "https://jwxt.gdupt.edu.cn/xskccjxx!getDataList.action";

    private static CloseableHttpClient httpClient = HttpClients.createDefault();

    @Autowired
    private IIAchievementService achievementService;

    @Autowired
    private AchievementDao achievementDao;

    @Override
    public List<List<AchievementItem>> allAchievementByReq(String jsessionId, String studentId) {
        Map<String,String> paramsMap=new HashMap<>(4);
        paramsMap.put("page","1");
        paramsMap.put("rows","180");
        paramsMap.put("sort","xnxqdm");
        paramsMap.put("order","asc");
        // 所有成绩 包括 专业课 + 公选课
        List<BasicNameValuePair> paramsList = Arrays.asList(
                new BasicNameValuePair("page", "1"),
                new BasicNameValuePair("rows", "180"),
                new BasicNameValuePair("sort", "xnxqdm,zcj"),
                //
                new BasicNameValuePair("order", "asc"));
        UrlEncodedFormEntity urlEncodedFormEntity = null;
        try {
             urlEncodedFormEntity = new UrlEncodedFormEntity(paramsList);
        } catch (UnsupportedEncodingException e) {
            e.printStackTrace();
        }
        HttpPost httpPost = new HttpPost(URL);
        httpPost.setHeader("Cookie", "JSESSIONID=" + jsessionId);
        httpPost.setEntity(urlEncodedFormEntity);

        String content = null;
        try(CloseableHttpResponse response = httpClient.execute(httpPost)) {
            content = EntityUtils.toString(response.getEntity());
            // 各个学期的课进行排序, [1,2,3,4,5,6,7,8,9,10...n + 公选课]
            List<AchievementItem> acRspItemList = JSON.parseObject(content, AcRsp.class).getRows();
            // 已经按照学期排好序了, 按照学期进行分类即可
            TreeMap<String, List<AchievementItem>> map = new TreeMap<>();
            acRspItemList.forEach(a -> {

                // 公共选修课就单独的 00 map
                if (a.getKcdlmc().equals("公共选修课")) {
                    List<AchievementItem> list = map.getOrDefault("00", new ArrayList<>());
                    map.put("00", list);
                    list.add(a);
                    return;
                }

                String xnxqdm = a.getXnxqdm();
                List<AchievementItem> acRspItems = map.get(xnxqdm);
                if (acRspItems == null) {
                    List<AchievementItem> list = new ArrayList<>();
                    map.put(xnxqdm, list);
                    acRspItems = list;
                }
                acRspItems.add(a);
            });
            List<Achievement> list = new ArrayList<>();
            List<List<AchievementItem>> returnList = new ArrayList<>();
            for (Map.Entry<String, List<AchievementItem>> entry : map.entrySet()) {
                // 不止八个学期
                Achievement achievement = new Achievement(studentId, entry.getKey(), JSON.toJSONString(entry.getValue()));
                list.add(achievement);
                returnList.add(entry.getValue());
            }
            // 更新
            achievementDao.updateOrInsertAchievementBatch(list);
            convertGxk(returnList);

            response.close();

            return returnList;
        }catch (Exception e) {
            e.printStackTrace();
            log.error(content);
        }
        throw new RuntimeException("拉取所有成绩时出现错误");
    }

    @Override
    public List<List<AchievementItem>> allAchievementByDb(String studentId) {
        QueryWrapper<Achievement> q1 = new QueryWrapper<>();
        q1.eq("student_id", studentId);
        q1.orderByAsc("term");
        List<Achievement> achievementList = achievementService.list(q1);
        List<List<AchievementItem>> returnList = new ArrayList<>();
        for (Achievement achievement : achievementList) {
            List<AchievementItem> list = JSON.parseArray(achievement.getContent(), AchievementItem.class);
            if (list.size() != 0) {
                returnList.add(list);
            }
        }
        convertGxk(returnList);
        return returnList;
    }

    // 把公选课放在最前面
    private void convertGxk(List<List<AchievementItem>> list) {
        // "公共equals(achievementItemList.get(0).getKcdlmc()选修课".
        if (list.get(0) == null || list.get(0).size() == 0 || list.get(0).get(0) == null) {
            return;
        }
        if ("公共选修课".equals(list.get(0).get(0).getKcdlmc())) {
            return;
        }
        for (int i = 1; i < list.size(); i++) {
            List<AchievementItem> achievementItems = list.get(i);
            if ("公共选修课".equals(achievementItems.get(0).getKcdlmc())) {
                // 把这个放到最前面, 但是学期顺序又变了, 所以这里抛出错误
                throw new RuntimeException("公选课在中间");
            }
        }
    }

    @Data
    private static class AcRsp {

        private Integer total;

        private List<AchievementItem> rows;

    }

}
